#include <sys/types.h>
#include <sys/socket.h>
#include <stdio.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include <unistd.h>
#include <string.h>
#include <stdlib.h>
#include <fcntl.h>
#include <sys/shm.h>
#include <iostream>
#include <thread>
#include <vector>

using namespace std;


struct NetMsg {
    char    name[32];
    short   age;
    char    sex[16];
    float   height;
    float   weight;
};


class Client
{
public:
    Client(string ip, int port) :m_addr(ip), m_port(port) {}
    ~Client() {}
    void run();                     // 启动客户端服务
    static void SendMsg(int conn);  // 发送线程
    static void RecvMsg(int conn);  // 接收线程
private:
    int         m_port;             // 服务器端口
    string      m_addr;             // 服务器ip
    int         m_sockfd;           // 与服务器建立连接的套接字描述符
};

void Client::run()
{

    //定义 sockfd
    m_sockfd = socket(AF_INET, SOCK_STREAM, 0);

    //定义sockaddr_in
    struct sockaddr_in servaddr;
    memset(&servaddr, 0, sizeof(servaddr));
    servaddr.sin_family = AF_INET;
    servaddr.sin_port = htons(m_port);                      // 服务器端口
    servaddr.sin_addr.s_addr = inet_addr(m_addr.c_str());   // 服务器 ip

    // 连接服务器，成功返回0，错误返回-1
    if (connect(m_sockfd, (struct sockaddr *)&servaddr, sizeof(servaddr)) < 0)
    {
        perror("connect failed.");
        exit(1);
    }
    cout << "连接服务器成功\n";

    // 创建发送线程和接收线程
    thread send_t(SendMsg, m_sockfd), recv_t(RecvMsg, m_sockfd);
    send_t.join();
    cout << "发送线程已结束\n";
    recv_t.join();
    cout << "接收线程已结束\n";
    return;
}

void Client::SendMsg(int conn)
{
    while (1)
    {
        NetMsg msg;
        cout << "姓名：";
        cin >> msg.name;
        cout << "年龄：";
        cin >> msg.age;
        cout << "性别：";
        cin >> msg.sex;
        cout << "身高：";
        cin >> msg.height;
        cout << "体重：";
        cin >> msg.height;
        int ret = send(conn, &msg, sizeof(msg), 0); //发送
    }
}

void Client::RecvMsg(int conn)
{
    // 接收缓冲区
    char buffer[1000];
    // 不断接收数据
    while(1)
    {
        memset(buffer, 0, sizeof(buffer));
        int len = recv(conn, buffer, sizeof(buffer),0);
        cout << "收到服务器发来的信息：" << buffer << endl;
    }
}

int main(int argc, char* argv[])
{
    string addr = "127.0.0.1";
    short port = 8989;
    Client c(addr, port);
    c.run();
    return 0;
}